#include "cajero.h"
#include <QTime>
#include <mqueue.h>
#include <semaphore.h>
#include <stdio.h>
#include "ventanasimulacion.h"

Cajero::Cajero(int id, int saldo, QImage imagen) :
        id(id), saldo(saldo), imagen(imagen) {
    cantidadClientes = cantidadDepositos = cantidadRetiros = cantidadConsultas
        = cantidadServicios = totalIngreso = totalEgreso = retirosNot = 0;
}

void Cajero::setId(int id) {
    this->id = id;
}

int Cajero::getId() {
    return id;
}

void Cajero::setSaldo(int saldo) {
    this->saldo = saldo;
}

int Cajero::getSaldo() {
    return saldo;
}

void Cajero::setImagen(QImage imagen) {
    this->imagen=imagen;
}


void Cajero::setVentanaSimulacion(VentanaSimulacion* ventanaSimulacion) {
    this->ventanaSimulacion = ventanaSimulacion;
    connect(this, SIGNAL(clienteRetirado(int)), ventanaSimulacion, SLOT(retirar(int)));
}

bool Cajero::atenderCliente(QString cliente) {
    emit clienteRetirado(id);
    int monto = cliente.right(cliente.length() - 2).toInt();
    cantidadClientes++;
    switch (cliente[0].toAscii()) {
        case '1':
                if (saldo < monto) {
                    retirosNot++;
                    return false;
                }
                saldo -= monto;
                ++cantidadRetiros;
                totalEgreso+=monto;
                break;
        case '2':
                saldo += monto;
                ++cantidadDepositos;
                totalIngreso+=monto;
                break;
        case '3':
                ++cantidadConsultas;
                break;
        case '4':
                saldo += monto;
                ++cantidadServicios;
                totalIngreso+=monto;
                break;
    }
    return true;
}

void Cajero::run() {
    char str[8];
    char mensaje[8192];
    sprintf(str, "/cola%c", id + 96);
    while (true) {
        qsrand((uint)QTime::currentTime().msec());
        mqd_t buzon = mq_open(str, O_RDWR);
        if (buzon == (mqd_t) - 1)
            perror("Error al abrir la cola");

        sem_t* semaforo = sem_open(str, O_RDWR);
        if (semaforo == SEM_FAILED)
            perror("Error creando o abriendo el semaforo");
        msleep(qrand() % 2000 + 3000);
        if (mq_receive(buzon, mensaje, 8192, NULL) == -1)
            perror("Error recibiendo el mensaje");
        atenderCliente(QString(mensaje));
        sem_post(semaforo);
        mq_close(buzon);
        sem_close(semaforo);
    }
}

int Cajero::getCantClientes() {
    return cantidadClientes;
}

int Cajero::getCantidadDepositos() {
    return cantidadDepositos;
}

int Cajero::getCantidadRetiros() {
    return cantidadRetiros;
}

int Cajero::getCantidadConsultas() {
    return cantidadConsultas;
}

int Cajero::getCantidadServicios() {
    return cantidadServicios;
}

float Cajero::porcentajeOperacion(int parcial) {
    if (cantidadClientes != 0)
        return (parcial * 100) / cantidadClientes;
    else
        return 0;
}

float Cajero::getTotalIngreso() {
    return totalIngreso;
}

float Cajero::getTotalEgreso() {
    return totalEgreso;
}

int Cajero::getRetirosNot() {
    return retirosNot;
}

